package com.petmarket.client;

import com.petmarket.common.AccountManger;
import com.petmarket.common.CommonClient;
import com.petmarket.common.PageResult;
import com.petmarket.contract.LoginContract;
import com.petmarket.entity.LoginDetail;
import com.petmarket.uitls.SpringUtils;
import org.fisco.bcos.sdk.v3.BcosSDK;
import org.fisco.bcos.sdk.v3.codec.datatypes.generated.tuples.generated.Tuple2;
import org.fisco.bcos.sdk.v3.codec.datatypes.generated.tuples.generated.Tuple5;
import org.fisco.bcos.sdk.v3.model.TransactionReceipt;
import org.fisco.bcos.sdk.v3.transaction.model.exception.ContractException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.boot.ApplicationArguments;
import org.springframework.boot.ApplicationRunner;
import org.springframework.stereotype.Service;

import java.math.BigInteger;
import java.util.ArrayList;
import java.util.List;

@Service
public class LoginClient extends CommonClient implements ApplicationRunner {

    public static final Logger logger = LoggerFactory.getLogger(LoginClient.class.getName());

    public void insert(LoginDetail loginDetail) throws ContractException {
        LoginContract loginContract = (LoginContract) getContractMap().get("LoginDetails");
//        BigInteger count = loginContract.count(BigInteger.valueOf(0), BigInteger.valueOf(200)).add(BigInteger.valueOf(1));

        //BigInteger count = LogId.getLogId(loginContract);

        TransactionReceipt receipt = loginContract.insert(loginDetail.getId(),loginDetail.getAccount(),loginDetail.getPassword()
        ,loginDetail.getUserType(),"0", AccountManger.createAccountKey());
    }

    public LoginDetail query(LoginDetail loginDetail) throws ContractException {
        LoginContract loginContract = (LoginContract) getContractMap().get("LoginDetails");
        System.out.println("123" + loginDetail.getId());
        Tuple5<String,String,String,String,String> getValue = loginContract.select(loginDetail.getId());

        LoginDetail resLoginDetail = new LoginDetail();
        resLoginDetail.setId(loginDetail.getId());
        resLoginDetail.setAccount(getValue.getValue1());
        resLoginDetail.setPassword(getValue.getValue2());
        resLoginDetail.setUserType(getValue.getValue3());
        resLoginDetail.setIsDeleted(getValue.getValue4());
        resLoginDetail.setPrivateKey(getValue.getValue5());
        if(resLoginDetail.getIsDeleted().equals("1") || resLoginDetail.getAccount().equals("")){
            throw new RuntimeException("执行失败");
        }
        return resLoginDetail;
    }

    public void update(LoginDetail loginDetail) {
        LoginContract loginContract = (LoginContract) getContractMap().get("LoginDetails");
        TransactionReceipt receipt = loginContract.update(loginDetail.getId(),loginDetail.getAccount(),
                loginDetail.getPassword(),loginDetail.getUserType());
        logger.info("调用LoginClient的update方法");
        logger.info("结果：{}", receipt);
    }

    public void remove(LoginDetail loginDetail) throws ContractException {
        LoginContract loginContract = (LoginContract) getContractMap().get("LoginDetails");
        this.query(loginDetail);
        TransactionReceipt receipt = loginContract.remove(loginDetail.getId());
        logger.info("调用LoginClient的remove方法");
        logger.info("结果：{}", receipt);
    }


    @Override
    public void run(ApplicationArguments args) throws Exception {
        BcosSDK sdk = SpringUtils.getBean("bcosSDK");
        deploy("LoginDetails", LoginContract.class, sdk);
    }

    public List<String> check(LoginDetail loginDetail) throws ContractException {
        LoginContract loginContract = (LoginContract) getContractMap().get("LoginDetails");
        Tuple2<String, String> check = loginContract.check(loginDetail.getAccount(), loginDetail.getPassword());
        List<String> res = new ArrayList<>();
        if(check.getValue1().equals("0") || check.getValue2().equals("0")){
            throw new RuntimeException();
        }
        res.add(check.getValue1());
        res.add(check.getValue2());
        return res;
    }

    public PageResult<LoginDetail> getLoginPage(Integer pageNo, Integer pageSize) throws ContractException {
        PageResult<LoginDetail> pageResult = new PageResult<>();
        LoginContract loginContract = (LoginContract) getContractMap().get("LoginDetails");
        BigInteger start = BigInteger.valueOf((pageNo - 1) * pageSize);
        BigInteger end = BigInteger.valueOf(pageNo * pageSize);
        System.out.println("start:" + start + "end:" + end);
        List<LoginDetail> loginList = new ArrayList<>();
        int count = 0,begin = start.intValue() + 1,last = end.intValue();
        while(count < pageSize){
            LoginDetail loginDetail = this.queryInner(BigInteger.valueOf(begin));
            if(loginDetail.getIsDeleted().equals("1")){
                continue;
            }
            else if(loginDetail.getIsDeleted().equals("")){
                break;
            }
            loginList.add(loginDetail);
            count++;
            begin++;
        }
        pageResult.setRecords(loginList);
        return pageResult;
    }

    private LoginDetail queryInner(BigInteger id) throws ContractException {
        LoginContract loginContract = (LoginContract) getContractMap().get("LoginDetails");
        Tuple5<String, String, String, String, String> getValue = loginContract.select(id);
        LoginDetail loginDetail = new LoginDetail();
        loginDetail.setId(id);
        loginDetail.setAccount(getValue.getValue1());
        loginDetail.setPassword(getValue.getValue2());
        loginDetail.setUserType(getValue.getValue3());
        loginDetail.setIsDeleted(getValue.getValue4());
        return loginDetail;
    }
}
